﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using Spring.Context;

using System.Xml;
using System.Data;
using System.Configuration;
//using BookFinder.AmazonWS;
namespace BookFinder
{
    public class SearchAmazonAPI : ISearchAPI
    {
        private const String amazonSearchURL = "webservices.amazon.com";
        private String amazonSearchAPIKey = null;
        private String amazonSearchAPIUserKeyEnc = null; 
        //private const String amazonSearchCountry = "US";
        private const String amazonSearchRestricted = "Books";
        //private const String amazonSearchResultFormat = "rest"; // Will always be REST

        public bool sendSearchQuery(String searchString, ref BooksCollection searchResults)
        {
            if (ConfigurationManager.AppSettings["AWSAccessKey"] != null &&
                    ConfigurationManager.AppSettings["AWSSecretKey"] != null)
            {
                amazonSearchAPIKey = ConfigurationManager.AppSettings["AWSAccessKey"];
                amazonSearchAPIUserKeyEnc = ConfigurationManager.AppSettings["AWSSecretKey"];
            }
            else if (Environment.GetEnvironmentVariable("AMAZON_SEARCH_KEY") != null &&
                        Environment.GetEnvironmentVariable("AMAZON_PRIVATE_KEY") != null)
            {
                amazonSearchAPIKey = Environment.GetEnvironmentVariable("AMAZON_SEARCH_KEY").ToString();
                amazonSearchAPIUserKeyEnc = Environment.GetEnvironmentVariable("AMAZON_PRIVATE_KEY").ToString();            
            }
            else
                return false;
              
            // creates an instance of the helper class that will sign the request
            AmazonProductAdvtApi.SignedRequestHelper helper = 
               new AmazonProductAdvtApi.SignedRequestHelper(amazonSearchAPIKey, amazonSearchAPIUserKeyEnc, amazonSearchURL);

            // construct the search querystring that includes the service name
           String  requestString = "Service=AWSECommerceService"
                    // Version of the API
                    + "&Version=2011-08-01"//2009-03-31"
                    // Sets the name of the method called from the API
                    + "&Operation=ItemSearch"
                    // Associate tag Amazon uses to identify the associate sent the request to be able to pay him.
                    + "&AssociateTag=null"
                    // The category of products that will be searched (for the scope of this project it is fixed to 'Books')
                    + "&SearchIndex=" + amazonSearchRestricted
                    // Amazon categorizes the response into groups and each group has its set of returned values.
                    + "&ResponseGroup=Large"
                    // The search keyword
                    + "&Keywords=" + searchString;
           try
           {

               requestString = helper.Sign(requestString);
               HttpGetter httpGetter = new HttpGetter();
               String XMLresponse;
               XMLresponse = httpGetter.HttpGetRequest(requestString);

               XmlDocument xDoc = new XmlDocument();
               XmlNamespaceManager nsman = new XmlNamespaceManager(xDoc.NameTable);
               nsman.AddNamespace("aws", "http://webservices.amazon.com/AWSECommerceService/2011-08-01");

               xDoc.LoadXml(XMLresponse);
               
               string responseIsValid;
               // Gets the status of the request from the response.
               responseIsValid = xDoc.SelectSingleNode("/aws:ItemSearchResponse/aws:Items/aws:Request/aws:IsValid", nsman).InnerText;
               
               XmlNodeList x = xDoc.SelectNodes("/aws:ItemSearchResponse/aws:Items/aws:Item", nsman);
               // If the request isValid load the booksCollection searchResults from the xml
               if(responseIsValid.ToLower() == "true") 
                searchResults = fillBooksCollection(searchResults, nsman, x);
           }
          catch (Exception ex)
           {
               return false;
          }
           finally
           {
                           
           }

            return true;   
        }

        private static BooksCollection fillBooksCollection(BooksCollection searchResults, XmlNamespaceManager nsman, XmlNodeList x)
        {
            Book bookItem;
            foreach(XmlNode xNode in x)
            {
                bookItem = new Book();
                bookItem.DataSource = "Amazon";
                bookItem.SearchSource = SearchSourceType.Amazon;
                bookItem.Vendor = "Amazon";

                if(xNode.SelectSingleNode("aws:ItemAttributes/aws:Title",nsman) != null)
                {
                    bookItem.Title = xNode.SelectSingleNode("aws:ItemAttributes/aws:Title",nsman).InnerText;
                }
                
                bookItem.BookURL = xNode.SelectSingleNode("aws:DetailPageURL", nsman) != null ? xNode.SelectSingleNode("aws:DetailPageURL", nsman).InnerText : String.Empty;
                
                if (xNode.SelectSingleNode("aws:ItemAttributes/aws:Author", nsman) != null)
                {
                    bookItem.Author = xNode.SelectSingleNode("aws:ItemAttributes/aws:Author", nsman).InnerText;
                }

                if (xNode.SelectSingleNode("aws:ItemAttributes/aws:Publisher", nsman) != null)
                {
                    bookItem.Publisher = xNode.SelectSingleNode("aws:ItemAttributes/aws:Publisher", nsman).InnerText;
                }
                if (xNode.SelectSingleNode("aws:ItemAttributes/aws:PublicationDate", nsman) != null)
                {
                    bookItem.PublicationDate = xNode.SelectSingleNode("aws:ItemAttributes/aws:PublicationDate", nsman).InnerText;
                }
                if (xNode.SelectSingleNode("aws:MediumImage/aws:URL", nsman) != null)
                {
                    bookItem.BookCoverURL = xNode.SelectSingleNode("aws:MediumImage/aws:URL", nsman).InnerText;
                }

                

                bookItem.ISBN = xNode.SelectSingleNode("aws:ItemAttributes/aws:ISBN", nsman)!=null?xNode.SelectSingleNode("aws:ItemAttributes/aws:ISBN", nsman).InnerText:String.Empty;
                bookItem.ISBN = ISBNConverter.GetISBN13(bookItem.ISBN);

                if (xNode.SelectSingleNode("aws:ItemAttributes/aws:ProductGroup", nsman) != null)
                {
                    String strPrice = null;
                    bookItem.BookFormat = xNode.SelectSingleNode("aws:ItemAttributes/aws:Binding", nsman) != null ? xNode.SelectSingleNode("aws:ItemAttributes/aws:Binding", nsman).InnerText : "";

                    if (xNode.SelectSingleNode("aws:ItemAttributes/aws:ProductGroup", nsman).InnerText.ToLower() == "ebooks")
                    {
                        if (xNode.SelectSingleNode("aws:ItemAttributes/aws:ListPrice/aws:FormattedPrice", nsman) != null)
                        {
                            strPrice = xNode.SelectSingleNode("aws:ItemAttributes/aws:ListPrice/aws:FormattedPrice", nsman).InnerText;
                        }
                        
                    }
                    else if (xNode.SelectSingleNode("aws:Offers/aws:TotalOffers", nsman) != null)
                    {
                        
                        if (xNode.SelectSingleNode("aws:Offers/aws:TotalOffers", nsman) != null &&
                            int.Parse(xNode.SelectSingleNode("aws:Offers/aws:TotalOffers", nsman).InnerText) > 0)
                        {
                            strPrice = xNode.SelectSingleNode("aws:Offers/aws:Offer/aws:OfferListing/aws:Price/aws:FormattedPrice", nsman).InnerText;
                        }
                        else
                        {
                            if (xNode.SelectSingleNode("aws:OfferSummary/aws:LowestNewPrice/aws:FormattedPrice", nsman) != null)
                                strPrice = xNode.SelectSingleNode("aws:OfferSummary/aws:LowestNewPrice/aws:FormattedPrice", nsman).InnerText;
                        }

                       
                    }
                    
                    if (strPrice != null && strPrice[0] == '$')
                    {
                        strPrice = strPrice.Remove(0, 1);
                    }
                    if (strPrice != null)
                    {
                        bookItem.Price = Decimal.Parse(strPrice);
                    }
                    
                }
                 

                if (xNode.SelectSingleNode("aws:EditorialReviews", nsman) != null &&
                    xNode.SelectSingleNode("aws:EditorialReviews", nsman).FirstChild.SelectSingleNode("aws:Source", nsman) != null)
                {
                    if (xNode.SelectSingleNode("aws:EditorialReviews", nsman).FirstChild.SelectSingleNode("aws:Source", nsman).InnerText == "Product Description")
                    {
                        bookItem.Description = HttpContext.Current.Server.HtmlDecode(xNode.SelectSingleNode("aws:EditorialReviews", nsman).FirstChild.SelectSingleNode("aws:Content", nsman).InnerXml);

                    }
                }


                
                

                searchResults.Add(bookItem);
            }
            return searchResults;
    }

        
    }
}